package com.java110.mall.cart.storeOrderEngine;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.java110.core.factory.GenerateCodeFactory;
import com.java110.dto.app.AppDto;
import com.java110.dto.housekeeping.HousekeepingServDto;
import com.java110.dto.housekeeping.HousekeepingServPoolDto;
import com.java110.dto.housekeeping.HousekeepingServPoolUserDto;
import com.java110.dto.product.ProductCategoryDto;
import com.java110.dto.product.ProductDto;
import com.java110.dto.shop.ShopDto;
import com.java110.dto.vipUser.ShopVipAccountDto;
import com.java110.dto.storeOrder.StoreOrderCartPriceDto;
import com.java110.dto.storeOrder.StoreOrderUserRoleDto;
import com.java110.dto.storeOrder.StoreOrderCartDto;
import com.java110.dto.storeOrder.StoreOrderCartEventDto;
import com.java110.dto.storeOrder.StoreOrderCartFeeDto;
import com.java110.dto.storeOrder.StoreOrderDiscountDto;
import com.java110.dto.user.UserAddressDto;
import com.java110.intf.acct.IShopVipAccountDetailInnerServiceSMO;
import com.java110.intf.acct.IShopVipAccountInnerServiceSMO;
import com.java110.intf.cart.*;
import com.java110.intf.goods.IHousekeepingServInnerServiceSMO;
import com.java110.intf.goods.IProductInnerServiceSMO;
import com.java110.intf.shop.IShopInnerServiceSMO;
import com.java110.intf.user.IUserAddressInnerServiceSMO;
import com.java110.po.housekeeping.HousekeepingServPoolPo;
import com.java110.po.housekeeping.HousekeepingServPoolUserPo;
import com.java110.po.shop.ShopVipAccountPo;
import com.java110.po.shop.ShopVipAccountDetailPo;
import com.java110.po.storeOrder.StoreCartPo;
import com.java110.po.storeOrder.StoreOrderPo;
import com.java110.po.storeOrder.StoreOrderCartPo;
import com.java110.po.storeOrder.StoreOrderCartEventPo;
import com.java110.po.storeOrder.StoreOrderCartFeePo;
import com.java110.po.storeOrder.StoreOrderDiscountPo;
import com.java110.utils.util.Assert;
import com.java110.utils.util.DateUtil;
import com.java110.utils.util.ListUtil;
import com.java110.utils.util.StringUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.List;

/**
 * @ClassName StoreOrderCartEngine
 * @Description TODO
 * @Author wuxw
 * @Date 2022/5/21 0:31
 * @Version 1.0
 * add by wuxw 2022/5/21
 **/

@Component
public class StoreOrderCartEngine {

    @Autowired
    StoreOrderComputePrice storeOrderComputePrice;

    @Autowired
    private IShopInnerServiceSMO shopInnerServiceSMOImpl;

    @Autowired
    private IStoreOrderCartInnerServiceSMO storeOrderCartInnerServiceSMOImpl;

    @Autowired
    private IStoreOrderCartEventInnerServiceSMO storeOrderCartEventInnerServiceSMOImpl;


    @Autowired
    private IHousekeepingServPoolInnerServiceSMO housekeepingServPoolInnerServiceSMOImpl;

    @Autowired
    private IHousekeepingServPoolUserInnerServiceSMO housekeepingServPoolUserInnerServiceSMOImpl;

    @Autowired
    private IHousekeepingServInnerServiceSMO housekeepingServInnerServiceSMOImpl;

    @Autowired
    private IUserAddressInnerServiceSMO userAddressInnerServiceSMOImpl;

    @Autowired
    private IStoreOrderCartFeeInnerServiceSMO storeOrderCartFeeInnerServiceSMOImpl;

    @Autowired
    private IHousekeepingFeeConfigInnerServiceSMO housekeepingFeeConfigInnerServiceSMOImpl;


    @Autowired
    private IStoreOrderDiscountInnerServiceSMO storeOrderDiscountInnerServiceSMOImpl;


    @Autowired
    private IProductInnerServiceSMO productInnerServiceSMOImpl;

    @Autowired
    private IShopVipAccountInnerServiceSMO shopVipAccountInnerServiceSMOImpl;
    @Autowired
    private IShopVipAccountDetailInnerServiceSMO shopVipAccountDetailInnerServiceSMOImpl;

    @Autowired
    private IStoreCartInnerServiceSMO storeCartInnerServiceSMOImpl;

    public List<StoreOrderCartPo> doGoods(StoreOrderPo storeOrderPo, JSONArray goodsList, StoreOrderUserRoleDto storeOrderUserRoleDto, JSONObject param) {

        List<StoreOrderCartPo> storeOrderCartPos = new ArrayList<>();
        if (ListUtil.isNull(goodsList)) {
            return storeOrderCartPos;
        }
        JSONObject goods = null;
        for (int goodsIndex = 0; goodsIndex < goodsList.size(); goodsIndex++) {
            goods = goodsList.getJSONObject(goodsIndex);
            saveStoreOrderCart(goods, storeOrderPo, storeOrderUserRoleDto,storeOrderCartPos,param);

        }

        return storeOrderCartPos;
    }

    /**
     * 保存购物车
     *
     * @param goods        商品
     * @param storeOrderPo
     */
    private void saveStoreOrderCart(JSONObject goods, StoreOrderPo storeOrderPo, StoreOrderUserRoleDto storeOrderUserRoleDto, List<StoreOrderCartPo> storeOrderCartPos, JSONObject param) {

        validateGoodsInfo(goods);

        //goods 刷入商铺信息
        goods.put("shopId",param.getString("shopId"));

        // 计算价格 并且校验库存，库存递减
        StoreOrderCartPriceDto storeOrderCartPriceDto = storeOrderComputePrice.computePriceAndValidateStock(goods, storeOrderUserRoleDto);

        ShopDto shopDto = new ShopDto();
        shopDto.setShopId(param.getString("shopId"));
        List<ShopDto> shopDtos = shopInnerServiceSMOImpl.queryShops(shopDto);

        Assert.listOnlyOne(shopDtos, "商铺不存在");

        //校验 库存

        // 保存购物车
        StoreOrderCartPo storeOrderCartPo = doSaveStoreOrderCart(goods, storeOrderPo, storeOrderCartPriceDto, shopDtos.get(0));

        storeOrderCartPos.add(storeOrderCartPo);

        //如果商品又优惠写入优惠
        if (goods.containsKey("discountPrice") && !StringUtil.isEmpty(goods.getString("discountPrice"))) {
            dealGoodsDiscountPrice(goods, storeOrderPo);
        }

        //积分商品扣积分
        if (isIntegralProduct(param.getString("shopId"), goods.getString("productId"))) {
            withholdAccount(storeOrderCartPo, storeOrderPo, param);
        }

        //保存事件
        doSaveStoreOrderCartEvent(goods, storeOrderPo, storeOrderCartPo);

        storeOrderPo.setOrderType("3306");

        //处理 家政服务
        saveHoursekeepingPool(storeOrderCartPo, storeOrderPo, goods, param.getString("addressId"));

        //师延俊加入 订单费用逻辑
        saveStoreOrderCartFee(storeOrderCartPo, storeOrderPo, goods);

        //删除购物车中的数据
        StoreCartPo storeCartPo = new StoreCartPo();
        storeCartPo.setValueId(goods.getString("valueId"));
        storeCartPo.setShopId(goods.getString("shopId"));
        storeCartInnerServiceSMOImpl.deleteStoreCart(storeCartPo);

    }


    private void doSaveStoreOrderCartEvent(JSONObject goods, StoreOrderPo storeOrderPo, StoreOrderCartPo storeOrderCartPo) {
        StoreOrderCartEventPo storeOrderCartEventPo = new StoreOrderCartEventPo();
        storeOrderCartEventPo.setCartId(storeOrderCartPo.getCartId());
        storeOrderCartEventPo.setOrderId(storeOrderCartPo.getOrderId());
        storeOrderCartEventPo.setEventId(GenerateCodeFactory.getGeneratorId(GenerateCodeFactory.CODE_PREFIX_eventId));
        storeOrderCartEventPo.setEventObjType("U");
        storeOrderCartEventPo.setEventObjId(storeOrderPo.getPersonId());
        storeOrderCartEventPo.setShopId(goods.getString("shopId"));
        storeOrderCartEventPo.setEventType(StoreOrderCartEventDto.EVENT_TYPE_COMMON);
        storeOrderCartEventPo.setEventMsg("用户下单");

        int flag = storeOrderCartEventInnerServiceSMOImpl.saveStoreOrderCartEvent(storeOrderCartEventPo);

        if (flag < 1) {
            throw new IllegalArgumentException("保存购物车事件失败");
        }

    }

    private StoreOrderCartPo doSaveStoreOrderCart(JSONObject goods, StoreOrderPo storeOrderPo, StoreOrderCartPriceDto storeOrderCartPriceDto, ShopDto shopDto) {
        int flag;
        StoreOrderCartPo storeOrderCartPo = new StoreOrderCartPo();
        storeOrderCartPo.setCartId(GenerateCodeFactory.getGeneratorId(GenerateCodeFactory.CODE_PREFIX_cartId));
        storeOrderCartPo.setExtCartId(goods.getString("cartId"));
        storeOrderCartPo.setCartNum(goods.getString("goodsNum"));
        storeOrderCartPo.setFreightPrice("0");
        storeOrderCartPo.setOrderId(storeOrderPo.getOrderId());
        storeOrderCartPo.setPayPrice(storeOrderCartPriceDto.getPayPrice() + "");
        storeOrderCartPo.setPersonId(storeOrderPo.getPersonId());
        storeOrderCartPo.setProductId(goods.getString("productId"));
        storeOrderCartPo.setState(StoreOrderCartDto.STATE_WAIT_BUY);
        storeOrderCartPo.setCartType(goods.getString("cartType"));
        if (!goods.containsKey("cartType")) {
            storeOrderCartPo.setCartType(StoreOrderCartDto.CART_TYPE_PRODUCT);
        }
        if (AppDto.MALL_APP_ID.equals(storeOrderPo.getAppId())) {
            storeOrderCartPo.setState(StoreOrderCartDto.STATE_FINISH);
        }

        storeOrderCartPo.setStoreId(shopDto.getStoreId());
        storeOrderCartPo.setShopId(goods.getString("shopId"));
        storeOrderCartPo.setValueId(goods.getString("valueId"));
        storeOrderCartPo.setPrice(storeOrderCartPriceDto.getPrice() + "");
        storeOrderCartPo.setRemark(goods.getString("remark"));
        storeOrderCartPo.setProdName(storeOrderCartPriceDto.getProdName());
        storeOrderCartPo.setAreaCode(goods.getString("areaCode"));
        storeOrderCartPo.setDeduction(storeOrderCartPriceDto.getDeduction() + "");


        System.out.println("======================================================================================================================");
        System.out.println(goods.getString("extProdId"));
        System.out.println(goods.getString("extValueId"));
        System.out.println(goods.getString("suType"));
        System.out.println(goods.getString("csId"));
        storeOrderCartPo.setExtProdId(goods.getString("extProdId"));

        storeOrderCartPo.setExtValueId(goods.getString("extValueId"));
        storeOrderCartPo.setSuType(goods.getString("suType"));
        storeOrderCartPo.setCsId(goods.getString("csId"));

        flag = storeOrderCartInnerServiceSMOImpl.saveStoreOrderCart(storeOrderCartPo);
        if (flag < 1) {
            throw new IllegalArgumentException("保存购物车失败");
        }
        return storeOrderCartPo;
    }


    private void validateGoodsInfo(JSONObject goods) {
        Assert.hasKeyAndValue(goods, "productId", "未包含商品");
        Assert.hasKeyAndValue(goods, "prodName", "未包含商品");
        Assert.hasKeyAndValue(goods, "valueId", "未包含商品规格");
        Assert.hasKeyAndValue(goods, "goodsNum", "未包含商品数量");
        //Assert.hasKeyAndValue(goods, "storeId", "未包含商户");
        Assert.hasKeyAndValue(goods, "shopId", "未包含商户");

        if (!goods.containsKey("cartId") || goods.getString("cartId").startsWith("-")) {
            goods.put("cartId", GenerateCodeFactory.getGeneratorId(GenerateCodeFactory.CODE_PREFIX_cartId));
        }
    }

    /**
     * 家政 服务走工单池
     *
     * @param storeOrderCartPo
     */
    private void saveHoursekeepingPool(StoreOrderCartPo storeOrderCartPo, StoreOrderPo storeOrderPo, JSONObject goods, String addressId) {
        //判断是否为 家政服务
        if (!StoreOrderCartDto.CART_TYPE_SERV.equals(goods.getString("cartType"))) {
            return;
        }
        storeOrderPo.setOrderType("3307");
        UserAddressDto userAddressDto = new UserAddressDto();
        userAddressDto.setAddressId(addressId);
        userAddressDto.setUserId(storeOrderPo.getPersonId());
        List<UserAddressDto> userAddressDtos = userAddressInnerServiceSMOImpl.queryUserAddresss(userAddressDto);

        Assert.listOnlyOne(userAddressDtos, "未找到收货人信息");

        userAddressDto = userAddressDtos.get(0);
        HousekeepingServPoolPo housekeepingServPoolPo = new HousekeepingServPoolPo();
        housekeepingServPoolPo.setApplyName(userAddressDto.getUsername());
        housekeepingServPoolPo.setApplyTel(userAddressDto.getTel());
        housekeepingServPoolPo.setAppointmentTime(goods.getString("appointmentTime"));
        housekeepingServPoolPo.setCartId(storeOrderCartPo.getCartId());
        housekeepingServPoolPo.setContext(storeOrderCartPo.getRemark());
        housekeepingServPoolPo.setObjId("-1");
        housekeepingServPoolPo.setObjName("未获取");
        housekeepingServPoolPo.setObjType("1001");
        housekeepingServPoolPo.setPoolId(GenerateCodeFactory.getGeneratorId("11"));
        housekeepingServPoolPo.setServId(storeOrderCartPo.getProductId());

        HousekeepingServDto housekeepingServDto = new HousekeepingServDto();
        housekeepingServDto.setServId(storeOrderCartPo.getProductId());
        housekeepingServDto.setShopId(storeOrderCartPo.getShopId());
        List<HousekeepingServDto> housekeepingServDtos = housekeepingServInnerServiceSMOImpl.queryHousekeepingServs(housekeepingServDto);

        Assert.listOnlyOne(housekeepingServDtos, "未找到服务");

        housekeepingServPoolPo.setServName(housekeepingServDtos.get(0).getServName());
        housekeepingServPoolPo.setShopId(storeOrderCartPo.getShopId());
        housekeepingServPoolPo.setState(HousekeepingServPoolDto.STATE_WAIT);
        int flag = housekeepingServPoolInnerServiceSMOImpl.saveHousekeepingServPool(housekeepingServPoolPo);

        if (flag < 1) {
            throw new IllegalArgumentException("保存家政服务工单池失败");
        }

        HousekeepingServPoolUserPo housekeepingServPoolUserPo = new HousekeepingServPoolUserPo();
        housekeepingServPoolUserPo.setContext(userAddressDto.getUsername() + "提交订单");
        housekeepingServPoolUserPo.setEndTime(DateUtil.getNow(DateUtil.DATE_FORMATE_STRING_A));
        housekeepingServPoolUserPo.setPoolEvent(HousekeepingServPoolUserDto.POOL_EVENT_START_USER);
        housekeepingServPoolUserPo.setPoolId(housekeepingServPoolPo.getPoolId());
        housekeepingServPoolUserPo.setPreRuId("-1");
        housekeepingServPoolUserPo.setPreStaffId("-1");
        housekeepingServPoolUserPo.setPreStaffName("无");
        housekeepingServPoolUserPo.setRuId(GenerateCodeFactory.getGeneratorId(GenerateCodeFactory.CODE_PREFIX_ruId));
        housekeepingServPoolUserPo.setShopId(housekeepingServPoolPo.getShopId());
        housekeepingServPoolUserPo.setStaffId(storeOrderPo.getPersonId());
        housekeepingServPoolUserPo.setStaffName(userAddressDto.getUsername());
        housekeepingServPoolUserPo.setStartTime(DateUtil.getNow(DateUtil.DATE_FORMATE_STRING_A));
        housekeepingServPoolUserPo.setState(HousekeepingServPoolUserDto.STATE_SUBMIT);
        flag = housekeepingServPoolUserInnerServiceSMOImpl.saveHousekeepingServPoolUser(housekeepingServPoolUserPo);

        if (flag < 1) {
            throw new IllegalArgumentException("保存家政服务工单池失败");
        }


    }

    /**
     * 写订单费用
     *
     * @param storeOrderCartPo
     * @param storeOrderPo
     * @param goods
     */
    private void saveStoreOrderCartFee(StoreOrderCartPo storeOrderCartPo, StoreOrderPo storeOrderPo, JSONObject goods) {

        //判断是否为 家政服务
        StoreOrderCartFeePo storeOrderCartFeePo = new StoreOrderCartFeePo();
        storeOrderCartFeePo.setDetailId(GenerateCodeFactory.getGeneratorId(GenerateCodeFactory.CODE_PREFIX_detailId));
        storeOrderCartFeePo.setCartId(storeOrderCartPo.getCartId());
        storeOrderCartFeePo.setShopId(storeOrderCartPo.getShopId());
        storeOrderCartFeePo.setFeeConfigId("-1");
        storeOrderCartFeePo.setFeeName(storeOrderCartPo.getProdName());
        storeOrderCartFeePo.setPrice(storeOrderCartPo.getPrice());
        storeOrderCartFeePo.setPayPrice(storeOrderCartPo.getPayPrice());
        storeOrderCartFeePo.setPayWay(goods.getString("payWay"));
        if (isIntegralProduct(storeOrderCartPo.getShopId(), storeOrderCartPo.getProductId())) {
            storeOrderCartFeePo.setPayWay(StoreOrderCartFeeDto.PAY_WAY_INTEGRAL);
        }
        //手机端支付
        if (AppDto.MALL_USER_APP_ID.equals(storeOrderPo.getAppId())) {
            storeOrderCartFeePo.setPayWay(StoreOrderCartFeeDto.PAY_WAY_WECHAT);
        }
        if (StringUtil.isEmpty(storeOrderCartFeePo.getPayWay())) {
            storeOrderCartFeePo.setPayWay(StoreOrderCartFeeDto.PAY_WAY_CASH);
        }

        //1001 未支付、2002 已支付
        storeOrderCartFeePo.setState(StoreOrderCartFeeDto.STATE_W);
        storeOrderCartFeePo.setExtOrderId("-1");
        if (StringUtil.isEmpty(storeOrderCartPo.getRemark())
                || StringUtil.isEmpty(storeOrderPo.getRemark())) {
            storeOrderCartFeePo.setRemark("");
        } else {
            storeOrderCartFeePo.setRemark(storeOrderCartPo.getRemark() + '和' + storeOrderPo.getRemark());
        }
        storeOrderCartFeePo.setUpdateTime(DateUtil.getNow("yyyy-MM-dd HH:mm:ss"));
        int flag = storeOrderCartFeeInnerServiceSMOImpl.saveStoreOrderCartFee(storeOrderCartFeePo);
        if (flag < 1) {
            throw new IllegalArgumentException("订单费用失败");
        }
    }

    /**
     * 处理商品优惠
     *
     * @param goods
     * @param storeOrderPo
     */
    private void dealGoodsDiscountPrice(JSONObject goods, StoreOrderPo storeOrderPo) {
        double discountPrice = goods.getDouble("discountPrice");
        if (discountPrice == 0) { // 没有优惠
            return;
        }

        StoreOrderDiscountPo storeOrderDiscountPo = new StoreOrderDiscountPo();
        storeOrderDiscountPo.setDiscountId(GenerateCodeFactory.getGeneratorId(GenerateCodeFactory.CODE_PREFIX_discountId));
        storeOrderDiscountPo.setDiscountObjId(goods.getString("cartId"));
        storeOrderDiscountPo.setDiscountObjType(StoreOrderDiscountDto.DISCOUNT_OBJ_TYPE_CART);
        storeOrderDiscountPo.setDiscountPrice(discountPrice + "");
        storeOrderDiscountPo.setDiscountRate(goods.getString("discountRate"));
        storeOrderDiscountPo.setDiscountType(goods.getString("discountType"));
        storeOrderDiscountPo.setShopId(goods.getString("shopId"));
        int flag = storeOrderDiscountInnerServiceSMOImpl.saveStoreOrderDiscount(storeOrderDiscountPo);
        if (flag < 1) {
            throw new IllegalArgumentException("记录优惠信息失败");
        }
    }

    //判断是否为积分商品
    private boolean isIntegralProduct(String shopId, String productId) {

        ProductDto productDto = new ProductDto();
        productDto.setShopId(shopId);
        productDto.setProductId(productId);
        List<ProductDto> productDtos = productInnerServiceSMOImpl.queryProducts(productDto);

        if (productDtos == null || productDtos.size() < 1) {
            return false;
        }

        String cateType = productDtos.get(0).getCateType();
        if (ProductCategoryDto.CATE_TYPE_INTEGRAL_PUBLIC.equals(cateType)) {
            return true;
        }
        return false;

    }

    private void withholdAccount(StoreOrderCartPo storeOrderCartPo, StoreOrderPo storeOrderPo, JSONObject param) {
        JSONObject vipuser = param.getJSONObject("vipUsers");
        if (null == vipuser || vipuser.size() < 1) {
            throw new IllegalArgumentException("未包含会员信息");
        }

        if (StringUtil.isNullOrNone(vipuser.getString("vipId"))) {
            throw new IllegalArgumentException("未包含会员信息");
        }


        ShopVipAccountDto shopVipAccountDto = new ShopVipAccountDto();
        shopVipAccountDto.setVipId(vipuser.getString("vipId"));
        shopVipAccountDto.setAcctType(ShopVipAccountDto.ACCT_TYPE_INTEGRAL);
        List<ShopVipAccountDto> shopVipAccountDtos = shopVipAccountInnerServiceSMOImpl.queryShopVipAccounts(shopVipAccountDto);
        if (shopVipAccountDtos == null || shopVipAccountDtos.size() < 1) {
            ShopVipAccountPo shopVipAccountPo = new ShopVipAccountPo();
            shopVipAccountPo.setVipAcctId(GenerateCodeFactory.getGeneratorId("11"));
            shopVipAccountPo.setAcctName("积分账户");
            shopVipAccountPo.setAmount("0");
            shopVipAccountPo.setShopId(storeOrderCartPo.getShopId());
            shopVipAccountPo.setStoreId(storeOrderCartPo.getStoreId());
            shopVipAccountPo.setVipId(vipuser.getString("vipId"));
            shopVipAccountPo.setAcctType("2004");
            int flag = shopVipAccountInnerServiceSMOImpl.saveShopVipAccount(shopVipAccountPo);
            if (flag < 1) {
                throw new IllegalArgumentException("新增积分账户失败");
            }
            ShopVipAccountDto vipAccountDto = new ShopVipAccountDto();
            vipAccountDto.setVipAcctId(shopVipAccountPo.getVipAcctId());
            vipAccountDto.setStoreId(shopVipAccountPo.getStoreId());
            vipAccountDto.setShopId(shopVipAccountPo.getShopId());
            vipAccountDto.setAmount(shopVipAccountPo.getAmount());
            vipAccountDto.setAcctType(shopVipAccountPo.getAcctType());
            shopVipAccountDtos.add(vipAccountDto);

        }

        //扣减积分
        ShopVipAccountDetailPo shopVipAccountDetailPo = new ShopVipAccountDetailPo();
        shopVipAccountDetailPo.setVipAcctId(shopVipAccountDtos.get(0).getVipAcctId());
        shopVipAccountDetailPo.setShopId(storeOrderCartPo.getShopId());
        shopVipAccountDetailPo.setOrderId(storeOrderPo.getOrderId());
        shopVipAccountDetailPo.setStoreId(storeOrderCartPo.getStoreId());
        shopVipAccountDetailPo.setAmount(storeOrderCartPo.getPayPrice());
        shopVipAccountDetailPo.setRemark("收银台累计积分");
        int flag = shopVipAccountInnerServiceSMOImpl.withholdAccount(shopVipAccountDetailPo);
        if (flag < 1) {
            throw new IllegalArgumentException("保存购物车失败");
        }

    }


}
